package com.xyzwps.server.paimon.spring

import com.xyzwps.server.paimon.error.Errors
import com.xyzwps.server.paimon.common.ReqCtx
import graphql.schema.DataFetchingEnvironment
import org.springframework.core.MethodParameter
import org.springframework.graphql.data.method.HandlerMethodArgumentResolver
import org.springframework.stereotype.Component

/**
 * @see org.springframework.graphql.data.method.annotation.support.ArgumentMethodArgumentResolver
 * @see org.springframework.graphql.data.method.annotation.support.ContextValueMethodArgumentResolver
 */
@Component
class AuthUserResolverForGraphQL : HandlerMethodArgumentResolver {
    override fun supportsParameter(parameter: MethodParameter): Boolean {
        return getAnno(parameter) != null
    }

    override fun resolveArgument(parameter: MethodParameter, environment: DataFetchingEnvironment): Any? {
        val ann = getAnno(parameter) ?: throw IllegalStateException("Expected @AuthUser annotation")
        val value = environment.graphQlContext.get<Any?>(ReqCtx.USER)
        if (ann.required && value == null) {
            throw Errors.UNAUTHENTICATED.toEx()
        }
        return value
    }

    private fun getAnno(parameter: MethodParameter) = parameter.getParameterAnnotation(AuthUser::class.java)

}
